using System;
using System.Data;
using Gtk;
using Npgsql;

public partial class MainWindow : Gtk.Window
{
	public MainWindow () : base(Gtk.WindowType.Toplevel)
	{
		Build ();
	
		string connectionString = "Server=localhost; DataBase=dbprueba; UserId=dbprueba; Password=sistemas";
		NpgsqlConnection dbConnection= new NpgsqlConnection(connectionString);
		dbConnection.Open();
		
		DataSet dataSet = new DataSet("dbPrueba");
	
		NpgsqlDataAdapter dataAdapter = new NpgsqlDataAdapter("SELECT * FROM articulo order by id", dbConnection);
		
		//	Recuperamos el esquema con sus claves primarias
		dataAdapter.MissingSchemaAction = MissingSchemaAction.AddWithKey;
	
		dataAdapter.Fill(dataSet);
		
///////////////////////////////////
//		1º MODIFICAMOS EL PRIMER REGISTRO...
///////////////////////////////////
		
//		Escogemos la tabla que hemos importado de la base de datos
		DataTable dataTable = dataSet.Tables[0];
		
//		Seleccionamos el último registro de la misma:
//		DataRow dataRow = dataTable.Rows[dataTable.Rows.Count-1];
//		Seleccionamos el primer registro de la misma ya que si las modificaciones las aplicamos al último
//		registro, como luego lo eliminamos no nos mostraría que ha habido un update de un registro
		DataRow dataRow = dataTable.Rows[0];
		
// 		Modificamos los campos 'nombre' y 'precio 
		dataRow["nombre"] = "articulo"+DateTime.Now;
		dataRow["precio"] = 666;	
	
///////////////////////////////////
//		2º ELIMINAMOS EL ULTIMO REGISTRO
///////////////////////////////////
		
		int ultimo = dataTable.Rows.Count -1;
		DataRow deleteDataRow = dataTable.Rows[ultimo];
		deleteDataRow.Delete();
		
///////////////////////////////////
//		3º AÑADIMOS UN REGISTRO...
///////////////////////////////////
				
		DataRow newDataRow = dataTable.NewRow();
		newDataRow["nombre"] = "articulo 777";
		newDataRow["precio"] = 18;
		newDataRow["categoria"] = 2;
		dataTable.Rows.Add(newDataRow);
	
		
//		Actualizamos los datos del dataSet
		new NpgsqlCommandBuilder(dataAdapter);
		
		//	Lanzamos un evento por cada registro que se actualiza antes de modificarlos en la base de datos.
		//	Para ello nos suscribimos al evento RowUpdating para ello
		dataAdapter.RowUpdating += delegate(object sender, NpgsqlRowUpdatingEventArgs e) 
		{
			if(e.StatementType == StatementType.Insert)
			{
				string insertSql = string.Format("{0}; select currval('articulo_id_seq') as id", e.Command.CommandText);
				e.Command.CommandText = insertSql;
			}
			Console.WriteLine("RowUpdating Command.CommandText={0}", e.Command.CommandText);
		};				
		
//		Los trasladamos a la base de datos actualizando así los datos que ésta contiene con los del DataSet. Lo comprobamos con el pgAdmin
		dataAdapter.Update(dataTable);
		
// 		Volvemos a visualizar los en el dataset y tambien lo comprobamos en la base de datos con el pgAdmin
		showDataSet(dataSet);
		
		dbConnection.Close();	
	}

	private void showDataSet(DataSet dataSet)
	{
		Console.WriteLine("DataSet Name={0}", dataSet.DataSetName);		
		foreach(DataTable datatable in dataSet.Tables)
		{
			showDataTable(datatable);
		}	
	}
	private void showDataTable(DataTable dataTable)
	{
		Console.WriteLine("DataTable Name={0}", dataTable.TableName);		
		foreach(DataRow dataRow in dataTable.Rows)
		{
			Console.WriteLine("DataTable Name={0}", dataTable.TableName);
			showDataRow(dataRow);
		}		
	}
	private void showDataRow(DataRow dataRow)
	{
		foreach(DataColumn dataColumn in dataRow.Table.Columns)
		{
			Console.WriteLine("{0}={1}", dataColumn.ColumnName, dataRow[dataColumn]);
		}			
	}
	protected void OnDeleteEvent (object sender, DeleteEventArgs a)
	{
		Application.Quit ();
		a.RetVal = true;
	}
}
